package com.dmcb.trade.business.crawlers.author;

import com.dmcb.common.business.constants.CommonConstant;
import com.dmcb.common.business.utils.RedisUtils;
import com.dmcb.common.web.conversion.JsonResult;
import com.dmcb.trade.business.constants.CrawlConstant;
import com.dmcb.trade.business.crawlers.article.ChuanSongMenParser;
import com.dmcb.trade.business.entities.Article;
import com.dmcb.trade.business.entities.Author;
import com.dmcb.trade.business.mappers.ArticleCrawlMapper;
import org.apache.commons.lang3.StringUtils;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Element;
import org.jsoup.select.Elements;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * 传送门根据作者主页导入全部文章
 * Created by 黑米 on 2016/11/16.
 */
@Service
public class ChuanSongMenCrawler extends BaseCrawler {
    Logger logger = LoggerFactory.getLogger(ChuanSongMenCrawler.class);

    @Autowired
    private ChuanSongMenParser chuanSongMenParser;
    @Autowired
    private ArticleCrawlMapper articleCrawlMapper;

    @Override
    protected String url() {
        return CrawlConstant.CHUANSONGMEN_URL;
    }

    @Override
    protected int tag() {
        return CrawlConstant.CHUANSONGMEN_TAG;
    }

    @Override
    protected String avatarSelect() {
        return "div.profile_photo>img";
    }

    @Override
    protected String channelNameSelect() {
        return "div.section_top>h3>div";
    }

    /**
     * 频道名称是否同时是作者名称
     *
     * @return 是、否
     */
    @Override
    protected boolean isAuthorName() {
        return true;
    }

    @Override
    protected String listSelect() {
        return "a.question_link";
    }

    @Override
    protected String titleSelect() {
        return "a.question_link";
    }

    @Override
    protected String authorLink() {
        return null;
    }

    @Override
    protected String authorSelect() {
        return "div.section_top>h3>div";
    }

    @Override
    protected JsonResult crawl(int authorId, String link, Author author, Document doc, boolean all) {
        // 爬取文章
        int page = 0;
        int totalAll = 0;
        List<Map<String, String>> mapList = new ArrayList<Map<String, String>>();
        try {
            while (page <= CrawlConstant.CRAWL_PAGE_TOTAL_CHUANSONGMEN) {
                if (doc == null) {
                    return error("获取文章列表失败，link=" + link + "?start=" + page);
                }
                Elements elements = doc.select(listSelect());
                if (elements == null || elements.size() == 0) {
                    break;
                }
                for (Element element : elements) {
                    Map<String, String> map = new HashMap<String, String>();
                    map.put("src", element.attr("href"));
                    map.put("title", element.text());
                    mapList.add(map);
                }
                doc = webClientUtil.getDoc(link + "?start=" + (page += 12));
                if (doc == null) {
                    RedisUtils.changeIP(15);
                    doc = webClientUtil.getDoc(link + "?start=" + page);
                }
            }
            JsonResult result = iterate2(authorId, mapList);
            if (!result.isSuccess()) {
                return result;
            }
            totalAll += result.getInt();
        } catch (Exception e) {
            logger.error(e.toString());
        }
        return totalAll == 0 ? error(CrawlConstant.MSG_WARN_NO_UPDATE) : success("总文章数：" + mapList.size() + ",成功导入：" + totalAll);
    }

    /**
     * 迭代解析、保存文章
     *
     * @return 成功保存数量
     */
    protected JsonResult iterate2(int authorId, List<Map<String, String>> mapList) {
        int succ = 0;
        try {
            for (Map<String, String> map : mapList) {
                // 获取标题、链接元素
                try {
                    // 校验作者、标题是否已存在
                    Article article = articleCrawlMapper.queryByAuthorTitle(authorId, map.get("title"));
                    if (article != null) {
                        continue;
                    }
                    String href = map.get("src");
                    if(StringUtils.isBlank(href)){
                        continue;
                    }
                    if( !href.startsWith("http://chuansong.me/")){
                        href="http://chuansong.me"+href;
                    }

                    JsonResult result = parse(authorId, href);
                    //如果导入文章出错，
                    succ += result.isSuccess() ? 1 : 0;
                } catch (Exception e) {
                    logger.error("Parser.parse error,{}", map.toString(), e);
                    return error(CommonConstant.ABNORMAL_MSG);
                }
            }

        } catch (Exception e) {
            logger.error(e.toString());
        }
        return success(succ);
    }


    @Override
    protected JsonResult parse(int authorId, String link) throws Exception {
        JsonResult json = chuanSongMenParser.parse(authorId, link);
        if (json.getStatus() == JsonResult.STATUS_ERROR) {
            RedisUtils.changeIP(15);
            json = chuanSongMenParser.parse(authorId, link);
        }
        return json;
    }



    @Override
    protected String getBody(Document doc) {
        return chuanSongMenParser.getBody(doc);
    }
}

